package main

import "fmt"

// 参考文章 https://www.fecmall.com/topic/1560

func x2(num int) int {
	return num * 2
}

//第二个参数，传递的是一个函数。
//注意这里的写法：完整的写出了这个函数的参数类型和返回类型。f是给这个函数参数取的形参名字。
func addOne(a int, f func( int) int) int {
	//实现功能：先加1，再做处理。具体怎么处理，要依赖传入的f函数
	a++
	return f(a)
}

func sub(a int, b int) int {
	return a - b
}

func pow(n int) int {
	return n * n
}

func main() {
	//第二个参数，传递的是一个函数名.
	fmt.Println(addOne(5, x2)) //实现功能：先加1，再乘2

	//这样写会报错，因为sub的函数类型不满足
	//fmt.Println(addOne(1,sub))

	// 既然是参数，那就有类型。函数作为参数来讲，也是有类型的。一个函数的输入参数和返回参数一致，就代表函数类型一样
	//pow函数，满足参数的要求
	fmt.Println(addOne(3, pow)) //实现功能：先加1，再平方

	//也可以直接在参数中，新写一个匿名函数作为参数传入
	re := addOne(3, func(x int) int {
		return x * 10
	})
	fmt.Println(re)
}
